Skip to content

Add a delegated executor: agent --executor claude-cli - #31

Merged
Shashankss1205 merged 1 commit into
mainfrom
feat/agent-delegated-executor
Jul 30, 2026
Merged

Add a delegated executor: agent --executor claude-cli#31
Shashankss1205 merged 1 commit into
mainfrom
feat/agent-delegated-executor

Conversation

@Shashankss1205

Copy link
Copy Markdown
Collaborator

The OpenClaw architecture, GraphARC-shaped. claude-cli/* cannot drive grapharc's own tool loop (no bind_tools — the CLI is a finished agent, not a completion API with tool schemas), so this gives it the inverse role: --executor claude-cli delegates the whole run to Claude Code's headless agent on the operator's subscription.

What grapharc keeps: the workspace boundary (cwd of the subprocess), --max-seconds enforced from outside, --max-turns forwarded, --allow/--deny mapped onto --allowedTools/--disallowedTools (tool names are Claude Code's), and start/end/stop trace events carrying the reported turns, tokens, cost and session id — so trace/metrics read a delegated run like any other.

What it says out loud: executor delegated, tokens labelled (reported) — the governance is Claude Code's permission model rather than grapharc's per-call gate, and the numbers are the sub-agent's own accounting. Coarser, and honest about it.

Refusals: --ask is refused headless (nobody to ask); a foreign --model is refused rather than silently ignored — with the documented exception that the openrouter default spec is treated as omitted, since argparse fills the same string either way.

Slack: --executor becomes a choice flag accepting sandbox and claude-cli, never local; a delegated run with no explicit tool globs gets --deny Bash injected — Claude Code's Bash is an unsandboxed shell on the host, which a bare Slack message should not carry. Explicit globs are a deliberate policy and pass through unmodified.

Tests: seven against a fake claude on PATH that logs its argv and prints a canned JSON report (forwarding, deny-mapping, model-tail extraction, foreign-model/ask/missing-binary refusals, trace shape and token arithmetic), plus gate tests for the executor choices and the Bash injection. Full suite green, ruff clean.

🤖 Generated with Claude Code

The claude CLI cannot be driven as a raw model (no bind_tools; it
exposes a finished agent, not a tool-calling completion API), so give
it the other role: --executor claude-cli hands the task, workspace and
tool policy to Claude Code's headless loop on the operator's
subscription. What grapharc keeps is the frame — workspace boundary,
wall clock enforced from outside, --allow/--deny mapped to
--allowedTools/--disallowedTools (names are Claude Code's), and
start/end/stop recorded to the trace with the reported turn and token
figures. The output names the trade: executor "delegated", tokens
"(reported)" — coarser governance, bought deliberately.

--ask is refused headless (nobody to ask); a non-claude-cli --model is
refused rather than silently ignored, except the openrouter default,
which argparse makes indistinguishable from --model being omitted.

From Slack, --executor accepts sandbox and claude-cli, never local,
and a delegated run with no explicit tool globs gets --deny Bash
injected: an unsandboxed host shell is not something a bare Slack
message should carry.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
@Shashankss1205
Shashankss1205 merged commit 0da93a6 into main Jul 30, 2026
6 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant